<?php

namespace App\Jobs;

use Carbon\Carbon;
use App\Models\Tag;
use App\Models\Sort;
use App\Models\Post;
use Illuminate\Contracts\Bus\SelfHandling;

class BlogIndexData extends Job implements SelfHandling
{
    protected $tag;
    protected $sort_id;

    /**
     * Constructor.
     *
     * @param string|null $tag
     */
    public function __construct($tag, $sort_id)
    {
        $this->tag = $tag;
        $this->sort_id = $sort_id;
    }

    /**
     * Execute the command.
     *
     * @return array
     */
    public function handle()
    {
        if ($this->tag) {
            return $this->tagIndexData($this->tag);
        }elseif($this->sort_id){
            return $this->sortIndexData($this->sort_id);
        }

        return $this->normalIndexData();
    }

    /**
     * Return data for normal index page.
     *
     * @return array
     */
    protected function normalIndexData()
    {
        $posts = Post::with('tags') // 渴求式加载 tags 模型
            ->where('published_at', '<=', Carbon::now())
            ->where('is_draft', 0)
            ->orderBy('published_at', 'desc')
            ->simplePaginate(config('blog.posts_per_page')); // 只显示上一页和下一页的简单分页方式

        return [
            'title' => config('blog.title'),
            'subtitle' => config('blog.subtitle'),
            'posts' => $posts,
            'page_image' => config('blog.page_image'),
            'meta_description' => config('blog.description'),
            'reverse_direction' => false,
            'tag' => null,
            'sort' => null,
        ];
    }

    /**
     * Return data for a tag index page.
     *
     * @param string $tag
     * @return array
     */
    protected function tagIndexData($tag)
    {
        $tag = Tag::where('tag', $tag)->firstOrFail();

        $reverse_direction = (bool) $tag->reverse_direction;

        $posts = Post::where('published_at', '<=', Carbon::now())
            ->whereHas('tags', function ($q) use ($tag) {
                $q->where('tag', '=', $tag->tag);
            })
            ->where('is_draft', 0)
            ->orderBy('published_at', $reverse_direction ? 'asc' : 'desc')
            ->simplePaginate(config('blog.posts_per_page'));

        $posts->addQuery('tag', $tag->tag);

        $page_image = $tag->page_image ?: config('blog.page_image');

        return [
            'title' => $tag->title,
            'subtitle' => $tag->subtitle,
            'posts' => $posts,
            'page_image' => $page_image,
            'tag' => $tag,
            'sort' => null,
            'reverse_direction' => $reverse_direction,
            'meta_description' => $tag->meta_description ?: \
                config('blog.description'),
        ];
    }
    /**
     * Return data for a sort index page.
     *
     * @param string $sort
     * @return array
     */
    protected function sortIndexData($sort_id)
    {
        $sort = Sort::where('id', $sort_id)->firstOrFail();

        $posts = Post::where('published_at', '<=', Carbon::now())
            ->whereHas('sort', function ($q) use ($sort) {
                $q->where('name', '=', $sort->name);
            })
            ->where('is_draft', 0)
            ->orderBy('published_at', 'desc')
            ->simplePaginate(config('blog.posts_per_page'));

        $posts->addQuery('sort_id', $sort->id);

        $page_image = $sort->page_image ?: config('blog.page_image');

        return [
            'posts' => $posts,
            'page_image' => $page_image,
            'sort' => $sort,
            'meta_description' => $sort->meta_description ?: \
                config('blog.description'),
            'tag' => null,
            'reverse_direction' => false,
        ];
    }
}
